package com.vip.mongofile.controller;

import com.vip.common.response.ErrorCode;
import com.vip.common.response.RestResponse;
import com.vip.common.response.RestResponses;
import com.vip.common.response.Result;
import com.vip.mongofile.constant.MongoConstant;
import com.vip.mongofile.model.MongoFile;
import com.vip.mongofile.service.component.FileStorageClient;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import java.io.UnsupportedEncodingException;
import java.util.List;
import java.util.Optional;

@Slf4j
@RestController
@RequestMapping("/api/mongo-file")
public class FileController {

    @Autowired
    private FileStorageClient fileStorageClient;

    /**
     * 分页查询文件
     *
     * @param pageNo
     * @param pageSize
     * @return
     */
    @GetMapping("/page")
    public RestResponse<List<MongoFile>> listFilesByPage(@RequestParam int pageNo, @RequestParam int pageSize) {
        return RestResponses.newResponseFromResult(fileStorageClient.listFilesByPage(pageNo, pageSize));
    }

    /**
     * 文件下载
     *
     * @param id
     * @return
     * @throws UnsupportedEncodingException
     */
    @GetMapping("/download/{id}")
    public ResponseEntity<Object> downloadFile(@PathVariable String id) throws UnsupportedEncodingException {
        MongoFile file = fileStorageClient.doGetFileById(id).getData();
        if (file != null) {
            return ResponseEntity.ok()
                    .header(HttpHeaders.CONTENT_DISPOSITION, "attachment; fileName=" + new String(file.getName().getBytes("utf-8"), "ISO-8859-1"))
                    .header(HttpHeaders.CONTENT_TYPE, "application/octet-stream")
                    .header(HttpHeaders.CONTENT_LENGTH, file.getSize() + "").header("Connection", "close")
                    .body(file.getContent().getData());
        } else {
            return ResponseEntity.status(HttpStatus.NOT_FOUND).body("File was not fount");
        }
    }

    /**
     * 文件详情
     *
     * @param id
     * @return
     */
    @GetMapping("/details/{id}")
    public RestResponse<MongoFile> fileDetails(@PathVariable String id) {
        Result<MongoFile> fileResult = fileStorageClient.doGetFileById(id);
        Optional<MongoFile> fileOptional = Optional.ofNullable(fileResult.getData());
        fileOptional.ifPresent(file -> {
            file.setContent(null);
            fileResult.setData(file);
        });
        return RestResponses.newResponseFromResult(fileResult);
    }

    /**
     * 在线显示文件
     *
     * @param id
     * @return
     */
    @GetMapping("/view/{id}")
    public ResponseEntity<Object> serveFileOnline(@PathVariable String id) throws UnsupportedEncodingException {
        MongoFile file = fileStorageClient.doGetFileById(id).getData();
        if (file != null) {
            if (!MongoConstant.VIEW_TYPE.contains(file.getSuffix().toLowerCase())) {
                return ResponseEntity.status(HttpStatus.NOT_FOUND)
                        .body(RestResponses.newFailResponse(ErrorCode.LOGIC_OBEY, "该文件不支持预览"));
            }
            return ResponseEntity.ok()
                    .header(HttpHeaders.CONTENT_DISPOSITION, "inline; fileName=" + new String(file.getName().getBytes("utf-8"), "ISO-8859-1"))
                    .header(HttpHeaders.CONTENT_TYPE, file.getContentType())
                    .header(HttpHeaders.CONTENT_LENGTH, file.getSize() + "").header("Connection", "close")
                    .body(file.getContent().getData());
        } else {
            return ResponseEntity.status(HttpStatus.NOT_FOUND).body("文件未找到");
        }
    }

    /**
     * 文件上传
     *
     * @param file
     * @return
     */
    @PostMapping("/upload")
    public RestResponse<MongoFile> fileUploadReturnPath(@RequestParam("file") MultipartFile file) {
        return RestResponses.newResponseFromResult(fileStorageClient.doUpload(file));
    }

    /**
     * 删除文件
     *
     * @param id
     * @return
     */
    @DeleteMapping("/del/{id}")
    public RestResponse<String> deleteFile(@PathVariable String id) {
        return RestResponses.newResponseFromResult(fileStorageClient.doDelete(id));
    }
}
